package validator

import (
	"fmt"
	"regexp"
	"strings"

	"kwdb-import/pkg/parser"
)

// SQLValidator SQL验证器
type SQLValidator struct {
	errors   []string
	warnings []string
}

// NewSQLValidator 创建新的验证器
func NewSQLValidator() *SQLValidator {
	return &SQLValidator{
		errors:   make([]string, 0),
		warnings: make([]string, 0),
	}
}

// ValidateStatements 验证SQL语句列表
func (v *SQLValidator) ValidateStatements(statements []parser.SQLStatement) error {
	v.errors = make([]string, 0)
	v.warnings = make([]string, 0)
	
	for i, stmt := range statements {
		if err := v.validateStatement(stmt, i+1); err != nil {
			v.errors = append(v.errors, fmt.Sprintf("第%d行: %v", stmt.Line, err))
		}
		
		// 检查警告
		warnings := v.checkWarnings(stmt)
		for _, warning := range warnings {
			v.warnings = append(v.warnings, fmt.Sprintf("第%d行: %s", stmt.Line, warning))
		}
	}
	
	if len(v.errors) > 0 {
		return fmt.Errorf("发现%d个错误:\n%s", len(v.errors), strings.Join(v.errors, "\n"))
	}
	
	return nil
}

// validateStatement 验证单个SQL语句
func (v *SQLValidator) validateStatement(stmt parser.SQLStatement, index int) error {
	sql := strings.TrimSpace(stmt.Content)
	
	// 检查语句是否为空
	if sql == "" {
		return fmt.Errorf("空语句")
	}
	
	// 检查语句是否以分号结尾
	if !strings.HasSuffix(sql, ";") {
		return fmt.Errorf("语句未以分号结尾")
	}
	
	// 根据语句类型进行特定验证
	switch stmt.Type {
	case parser.CreateTable:
		return v.validateCreateTable(sql)
	case parser.CreateDatabase:
		return v.validateCreateDatabase(sql)
	case parser.Insert:
		return v.validateInsert(sql)
	case parser.CreateIndex:
		return v.validateCreateIndex(sql)
	case parser.CreateView:
		return v.validateCreateView(sql)
	case parser.UseDatabase:
		return v.validateUseDatabase(sql)
	case parser.Unknown:
		return fmt.Errorf("未知的SQL语句类型")
	}
	
	return nil
}

// validateCreateTable 验证CREATE TABLE语句
func (v *SQLValidator) validateCreateTable(sql string) error {
	// 检查基本语法
	if !regexp.MustCompile(`(?i)^CREATE\s+TABLE\s+`).MatchString(sql) {
		return fmt.Errorf("CREATE TABLE语句语法错误")
	}
	
	// 检查表名
	tableNamePattern := regexp.MustCompile(`(?i)CREATE\s+TABLE\s+(?:IF\s+NOT\s+EXISTS\s+)?([\w\x60]+)`)
	matches := tableNamePattern.FindStringSubmatch(sql)
	if len(matches) < 2 {
		return fmt.Errorf("无法解析表名")
	}
	
	tableName := matches[1]
	if tableName == "" {
		return fmt.Errorf("表名为空")
	}
	
	// 检查是否包含列定义
	if !strings.Contains(sql, "(") || !strings.Contains(sql, ")") {
		return fmt.Errorf("CREATE TABLE语句缺少列定义")
	}
	
	return nil
}

// validateCreateDatabase 验证CREATE DATABASE语句
func (v *SQLValidator) validateCreateDatabase(sql string) error {
	if !regexp.MustCompile(`(?i)^CREATE\s+DATABASE\s+`).MatchString(sql) {
		return fmt.Errorf("CREATE DATABASE语句语法错误")
	}
	
	// 检查数据库名
	dbNamePattern := regexp.MustCompile(`(?i)CREATE\s+DATABASE\s+(?:IF\s+NOT\s+EXISTS\s+)?([\w\x60]+)`)
	matches := dbNamePattern.FindStringSubmatch(sql)
	if len(matches) < 2 {
		return fmt.Errorf("无法解析数据库名")
	}
	
	dbName := matches[1]
	if dbName == "" {
		return fmt.Errorf("数据库名为空")
	}
	
	return nil
}

// validateInsert 验证INSERT语句
func (v *SQLValidator) validateInsert(sql string) error {
	if !regexp.MustCompile(`(?i)^INSERT\s+INTO\s+`).MatchString(sql) {
		return fmt.Errorf("INSERT语句语法错误")
	}
	
	// 检查表名
	tableNamePattern := regexp.MustCompile(`(?i)INSERT\s+INTO\s+([\w\x60]+)`)
	matches := tableNamePattern.FindStringSubmatch(sql)
	if len(matches) < 2 {
		return fmt.Errorf("无法解析表名")
	}
	
	// 检查VALUES子句
	if !regexp.MustCompile(`(?i)\bVALUES\s*\(`).MatchString(sql) {
		return fmt.Errorf("INSERT语句缺少VALUES子句")
	}
	
	return nil
}

// validateCreateIndex 验证CREATE INDEX语句
func (v *SQLValidator) validateCreateIndex(sql string) error {
	if !regexp.MustCompile(`(?i)^CREATE\s+(UNIQUE\s+)?INDEX\s+`).MatchString(sql) {
		return fmt.Errorf("CREATE INDEX语句语法错误")
	}
	
	// 检查ON子句
	if !regexp.MustCompile(`(?i)\bON\s+[\w\x60]+\s*\(`).MatchString(sql) {
		return fmt.Errorf("CREATE INDEX语句缺少ON子句")
	}
	
	return nil
}

// validateCreateView 验证CREATE VIEW语句
func (v *SQLValidator) validateCreateView(sql string) error {
	if !regexp.MustCompile(`(?i)^CREATE\s+VIEW\s+`).MatchString(sql) {
		return fmt.Errorf("CREATE VIEW语句语法错误")
	}
	
	// 检查AS子句
	if !regexp.MustCompile(`(?i)\bAS\s+SELECT\s+`).MatchString(sql) {
		return fmt.Errorf("CREATE VIEW语句缺少AS SELECT子句")
	}
	
	return nil
}

// validateUseDatabase 验证USE语句
func (v *SQLValidator) validateUseDatabase(sql string) error {
	if !regexp.MustCompile(`(?i)^USE\s+`).MatchString(sql) {
		return fmt.Errorf("USE语句语法错误")
	}
	
	// 检查数据库名
	dbNamePattern := regexp.MustCompile(`(?i)USE\s+([\w\x60]+)`)
	matches := dbNamePattern.FindStringSubmatch(sql)
	if len(matches) < 2 {
		return fmt.Errorf("无法解析数据库名")
	}
	
	dbName := matches[1]
	if dbName == "" {
		return fmt.Errorf("数据库名为空")
	}
	
	return nil
}

// checkWarnings 检查警告
func (v *SQLValidator) checkWarnings(stmt parser.SQLStatement) []string {
	var warnings []string
	sql := strings.ToUpper(stmt.Content)
	
	// 检查可能不兼容的特性
	if strings.Contains(sql, "ENGINE=") {
		warnings = append(warnings, "包含MySQL特有的ENGINE选项，将被忽略")
	}
	
	if strings.Contains(sql, "AUTO_INCREMENT") {
		warnings = append(warnings, "包含AUTO_INCREMENT，将转换为SERIAL类型")
	}
	
	if strings.Contains(sql, "CHARSET") || strings.Contains(sql, "COLLATE") {
		warnings = append(warnings, "包含字符集或排序规则设置，将被忽略")
	}
	
	if strings.Contains(sql, "ENUM") {
		warnings = append(warnings, "包含ENUM类型，将转换为VARCHAR")
	}
	
	if strings.Contains(sql, "SET") && stmt.Type == parser.CreateTable {
		warnings = append(warnings, "包含SET类型，将转换为VARCHAR")
	}
	
	if stmt.Type == parser.CreateProcedure || stmt.Type == parser.CreateFunction || stmt.Type == parser.CreateTrigger {
		warnings = append(warnings, "存储过程/函数/触发器可能不被KWDB完全支持")
	}
	
	if strings.Contains(sql, "FULLTEXT") {
		warnings = append(warnings, "全文索引可能不被KWDB支持")
	}
	
	if strings.Contains(sql, "SPATIAL") {
		warnings = append(warnings, "空间索引可能不被KWDB支持")
	}
	
	return warnings
}

// GetErrors 获取错误列表
func (v *SQLValidator) GetErrors() []string {
	return v.errors
}

// GetWarnings 获取警告列表
func (v *SQLValidator) GetWarnings() []string {
	return v.warnings
}

// HasErrors 检查是否有错误
func (v *SQLValidator) HasErrors() bool {
	return len(v.errors) > 0
}

// HasWarnings 检查是否有警告
func (v *SQLValidator) HasWarnings() bool {
	return len(v.warnings) > 0
}

// Reset 重置验证器状态
func (v *SQLValidator) Reset() {
	v.errors = make([]string, 0)
	v.warnings = make([]string, 0)
}

// ValidateConnectionString 验证数据库连接字符串
func ValidateConnectionString(connStr string) error {
	if connStr == "" {
		return fmt.Errorf("连接字符串不能为空")
	}
	
	// 检查基本格式 (host:port/database)
	pattern := regexp.MustCompile(`^[^:]+:\d+/[^/]+$`)
	if !pattern.MatchString(connStr) {
		return fmt.Errorf("连接字符串格式错误，应为: host:port/database")
	}
	
	return nil
}

// ValidateCredentials 验证用户凭据
func ValidateCredentials(username, password string) error {
	if username == "" {
		return fmt.Errorf("用户名不能为空")
	}
	
	if password == "" {
		return fmt.Errorf("密码不能为空")
	}
	
	return nil
}